home *** CD-ROM | disk | FTP | other *** search
/ Gold Medal Software 3 / Gold Medal Software - Volume 3 (Gold Medal) (1994).iso / bbsutils / smb_110a.arj / CHKSMB.C < prev    next >
C/C++ Source or Header  |  1994-03-27  |  11KB  |  423 lines

  1. /* CHKSMB.C */
  2.  
  3. #include "smblib.h"
  4.  
  5. /****************************************************************************/
  6. /* Checks the disk drive for the existence of a file. Returns 1 if it       */
  7. /* exists, 0 if it doesn't.                                                 */
  8. /****************************************************************************/
  9. char fexist(char *filespec)
  10. {
  11.     struct ffblk f;
  12.  
  13. if(findfirst(filespec,&f,0)==0)
  14.     return(1);
  15. return(0);
  16. }
  17.  
  18.  
  19. char *usage="\nusage: chksmb [/opts] <filespec.SHD>\n"
  20.             "\n"
  21.             "opts:\n"
  22.             "       s - stop after errored message base\n"
  23.             "       p - pause after errored messsage base\n"
  24.             "       q - quiet mode (no beeps while checking)\n";
  25.  
  26. int main(int argc, char **argv)
  27. {
  28.     char        str[128],*p,*s,*beep="\7";
  29.     int         i,j,x,y,errors,errlast,stop_on_error=0,pause_on_error=0;
  30.     ulong        l,m,n,length,size,total=0,orphan=0,deleted=0,headers=0
  31.                 ,*offset,*number
  32.                 ,delhdrblocks,deldatblocks,hdrerr=0,lockerr=0,hdrnumerr=0
  33.                 ,dupenum=0,dupenumhdr=0,dupeoff=0,delidx=0,attr=0,actalloc=0
  34.                 ,delalloc=0,datactalloc=0,misnumbered=0,timeerr=0,idxofferr=0
  35.                 ,zeronum,idxzeronum,idxnumerr;
  36.     idxrec_t    idx;
  37.     smbmsg_t    msg;
  38.     smbstatus_t status;
  39.  
  40. printf("\nCHKSMB v1.10 · Checks Synchronet Message Base · Copyright 1994"
  41.     " Digital Dynamics\n");
  42.  
  43. if(argc<2) {
  44.     printf("%s",usage);
  45.     exit(1); }
  46.  
  47. errlast=errors=0;
  48. for(x=1;x<argc;x++) {
  49.     if(stop_on_error && errors)
  50.         break;
  51.     if(pause_on_error && errlast!=errors) {
  52.         printf("\7\nHit any key to continue...");
  53.         if(!getch())
  54.             getch();
  55.         printf("\n"); }
  56.     errlast=errors;
  57.     if(argv[x][0]=='/') {
  58.         for(y=1;argv[x][y];y++)
  59.             switch(toupper(argv[x][y])) {
  60.                 case 'Q':
  61.                     beep="";
  62.                     break;
  63.                 case 'P':
  64.                     pause_on_error=1;
  65.                     break;
  66.                 case 'S':
  67.                     stop_on_error=1;
  68.                     break;
  69.                 default:
  70.                     printf("%s",usage);
  71.                     exit(1); }
  72.         continue; }
  73.  
  74. strcpy(smb_file,argv[x]);
  75. p=strrchr(smb_file,'.');
  76. s=strrchr(smb_file,'\\');
  77. if(p>s) *p=0;
  78. strupr(smb_file);
  79.  
  80. sprintf(str,"%s.SHD",smb_file);
  81. if(!fexist(str)) {
  82.     printf("\n%s doesn't exist.\n",smb_file);
  83.     continue; }
  84.  
  85. printf("\nChecking %s Headers\n\n",smb_file);
  86.  
  87. if((i=smb_open(10))!=0) {
  88.     printf("smb_open returned %d\n",i);
  89.     errors++;
  90.     continue; }
  91.  
  92. if(filelength(fileno(shd_fp))<sizeof(smbhdr_t)) {
  93.     printf("Empty\n");
  94.     smb_close();
  95.     continue; }
  96.  
  97. if((i=smb_locksmbhdr(10))!=0) {
  98.     smb_close();
  99.     printf("smb_locksmbhdr returned %d\n",i);
  100.     errors++;
  101.     continue; }
  102.  
  103. if((i=smb_getstatus(&status))!=0) {
  104.     smb_unlocksmbhdr();
  105.     smb_close();
  106.     printf("smb_getstatus returned %d\n",i);
  107.     errors++;
  108.     continue; }
  109.  
  110.  
  111. length=filelength(fileno(shd_fp));
  112.  
  113.  
  114. if((length/SHD_BLOCK_LEN)*sizeof(ulong)) {
  115.     if((number=(ulong *)MALLOC(((length/SHD_BLOCK_LEN)+2)*sizeof(ulong)))
  116.         ==NULL) {
  117.         printf("Error allocating %lu bytes of memory\n"
  118.             ,(length/SHD_BLOCK_LEN)*sizeof(ulong));
  119.         return(++errors); } }
  120. else
  121.     number=NULL;
  122.  
  123. if((i=smb_open_ha(10))!=0) {
  124.     printf("smb_open_ha returned %d\n",i);
  125.     return(++errors); }
  126.  
  127. if((i=smb_open_da(10))!=0) {
  128.     printf("smb_open_da returned %d\n",i);
  129.     return(++errors); }
  130.  
  131. headers=deleted=orphan=dupenumhdr=attr=zeronum=timeerr=lockerr=hdrerr=0;
  132. delalloc=actalloc=datactalloc=deldatblocks=delhdrblocks=0;
  133.  
  134. for(l=status.header_offset;l<length;l+=size) {
  135.     printf("\r%2u%%  ",(long)(100.0/((float)length/l)));
  136.     msg.idx.offset=l;
  137.     if((i=smb_lockmsghdr(msg,10))!=0) {
  138.         printf("\n(%06lX) smb_lockmsghdr returned %d\n",l,i);
  139.         lockerr++;
  140.         headers++;
  141.         size=SHD_BLOCK_LEN;
  142.         continue; }
  143.     if((i=smb_getmsghdr(&msg))!=0) {
  144.         smb_unlockmsghdr(msg);
  145.         fseek(sha_fp,(l-status.header_offset)/SHD_BLOCK_LEN,SEEK_SET);
  146.         j=fgetc(sha_fp);
  147.         if(j) {             /* Allocated block or at EOF */
  148.             printf("%s\n(%06lX) smb_getmsghdr returned %d\n",beep,l,i);
  149.             hdrerr++; }
  150.         else
  151.             delhdrblocks++;
  152.         size=SHD_BLOCK_LEN;
  153.         continue; }
  154.     smb_unlockmsghdr(msg);
  155.     printf("#%-5lu (%06lX) %-25.25s ",msg.hdr.number,l,msg.from);
  156.     if(msg.hdr.attr&MSG_DELETE) {
  157.         deleted++;
  158.         if(number)
  159.             number[headers]=0; }
  160.     else {
  161.  
  162.         if(msg.hdr.number>status.last_msg) {
  163.             printf("%sOut-Of-Range message number\n",beep);
  164.             hdrnumerr++; }
  165.  
  166.         if(smb_getmsgidx(&msg)) {
  167.             printf("%sNot found in index\n",beep);
  168.             orphan++; }
  169.         else if(msg.hdr.attr!=msg.idx.attr) {
  170.             printf("%sAttributes mismatch index\n",beep);
  171.             attr++; }
  172.         else if(msg.hdr.when_imported.time!=msg.idx.time) {
  173.             printf("%sImport date/time mismatch index\n",beep);
  174.             timeerr++; }
  175.  
  176.         if(msg.hdr.number==0) {
  177.             printf("%sZero message number\n",beep);
  178.             zeronum++; }
  179.         if(number) {
  180.             for(m=0;m<headers;m++)
  181.                 if(number[m] && msg.hdr.number==number[m]) {
  182.                     printf("%sDuplicate message number\n",beep);
  183.                     dupenumhdr++;
  184.                     break; }
  185.             number[headers]=msg.hdr.number; } }
  186.  
  187.     size=smb_getmsghdrlen(msg);
  188.     while(size%SHD_BLOCK_LEN)
  189.         size++;
  190.  
  191.     fseek(sha_fp,(l-status.header_offset)/SHD_BLOCK_LEN,SEEK_SET);
  192.     for(m=0;m<size;m+=SHD_BLOCK_LEN)
  193.         if(msg.hdr.attr&MSG_DELETE && (i=fgetc(sha_fp))!=0) {
  194.             printf("%sDeleted Header Block %lu marked %02X\n"
  195.                 ,beep,m/SHD_BLOCK_LEN,i);
  196.             delalloc++; }
  197.         if(!(msg.hdr.attr&MSG_DELETE) && (i=fgetc(sha_fp))!=1) {
  198.             printf("%sActive Header Block %lu marked %02X\n"
  199.                 ,beep,m/SHD_BLOCK_LEN,i);
  200.             actalloc++; }
  201.  
  202.     if(!(msg.hdr.attr&MSG_DELETE)) {
  203.         for(n=0;n<msg.hdr.total_dfields;n++) {
  204.             fseek(sda_fp
  205.                 ,((msg.hdr.offset+msg.dfield[n].offset)/SDT_BLOCK_LEN)*2
  206.                 ,SEEK_SET);
  207.             for(m=0;m<msg.dfield[n].length;m+=SDT_BLOCK_LEN) {
  208.                 fread(&i,2,1,sda_fp);
  209.                 if(i!=1) {
  210.                     printf("%sActive Data Block %lu.%lu marked %02X\n"
  211.                         ,beep,n,m/SHD_BLOCK_LEN,i);
  212.                     datactalloc++; } } } }
  213.     else
  214.         delhdrblocks+=(size/SHD_BLOCK_LEN);
  215.     headers++;
  216.     smb_freemsgmem(msg); }
  217.  
  218. if(number)
  219.     FREE(number);
  220.  
  221. printf("\r%79s\r100%%\n","");
  222.  
  223. printf("\nChecking %s Data Blocks\n\n",smb_file);
  224.  
  225. length=filelength(fileno(sda_fp));
  226.  
  227. fseek(sda_fp,0L,SEEK_SET);
  228. for(l=0;l<length;l+=2) {
  229.     printf("\r%2u%%  ",l ? (long)(100.0/((float)length/l)) : 0);
  230.     i=0;
  231.     if(!fread(&i,2,1,sda_fp))
  232.         break;
  233.     if(!i)
  234.         deldatblocks++; }
  235.  
  236. fclose(sha_fp);
  237. fclose(sda_fp);
  238.  
  239. printf("\r%79s\r100%%\n","");
  240.  
  241. total=filelength(fileno(sid_fp))/sizeof(idxrec_t);
  242.  
  243. dupenum=dupeoff=delidx=misnumbered=idxzeronum=idxnumerr=idxofferr=0;
  244.  
  245. if(total) {
  246.  
  247. printf("\nChecking %s Index\n\n",smb_file);
  248.  
  249. if((offset=(ulong *)MALLOC(total*sizeof(ulong)))==NULL) {
  250.     printf("Error allocating %lu bytes of memory\n",total*sizeof(ulong));
  251.     return(++errors); }
  252. if((number=(ulong *)MALLOC(total*sizeof(ulong)))==NULL) {
  253.     printf("Error allocating %lu bytes of memory\n",total*sizeof(ulong));
  254.     return(++errors); }
  255. fseek(sid_fp,0L,SEEK_SET);
  256.  
  257. for(l=0;l<total;l++) {
  258.     printf("\r%2lu%%  %5lu ",l ? (long)(100.0/((float)total/l)) : 0,l);
  259.     fread(&idx,sizeof(idxrec_t),1,sid_fp);
  260.     printf("#%-5lu (%06lX) 1st Pass ",idx.number,idx.offset);
  261.     if(idx.attr&MSG_DELETE) {
  262.         printf("%sMarked for deletion\n",beep);
  263.         delidx++; }
  264.     for(m=0;m<l;m++)
  265.         if(number[m]==idx.number) {
  266.             printf("%sDuplicate message number\n",beep);
  267.             dupenum++;
  268.             break; }
  269.     for(m=0;m<l;m++)
  270.         if(offset[m]==idx.offset) {
  271.             printf("%sDuplicate offset\n",beep,idx.offset);
  272.             dupeoff++;
  273.             break; }
  274.     if(idx.offset<status.header_offset) {
  275.         printf("%sInvalid offset\n",beep);
  276.         idxofferr++;
  277.         break; }
  278.     if(idx.number==0) {
  279.         printf("%sZero message number\n",beep);
  280.         idxzeronum++;
  281.         break; }
  282.     if(idx.number>status.last_msg) {
  283.         printf("%sOut-Of-Range message number\n",beep);
  284.         idxnumerr++;
  285.         break; }
  286.     number[l]=idx.number;
  287.     offset[l]=idx.offset; }
  288.  
  289. printf("\r%79s\r","");
  290. for(m=0;m<total;m++) {
  291.     printf("\r%2lu%%  %5lu ",m ? (long)(100.0/((float)total/m)) : 0,m);
  292.     printf("#%-5lu (%06lX) 2nd Pass ",number[m],offset[m]);
  293.     for(n=0;n<m;n++)
  294.         if(number[m] && number[n] && number[m]<number[n]) {
  295.             printf("%sMisordered message number\n",beep);
  296.             misnumbered++;
  297.             number[n]=0;
  298.             break; } }
  299. FREE(number);
  300. FREE(offset);
  301.  
  302. printf("\r%79s\r100%%\n","");
  303.  
  304. }
  305.  
  306.  
  307. printf("\n");
  308. printf("%-35.35s (=): %lu\n"
  309.     ,"Status Total"
  310.     ,status.total_msgs);
  311. printf("%-35.35s (=): %lu\n"
  312.     ,"Index Records"
  313.     ,total);
  314. printf("%-35.35s (=): %lu\n"
  315.     ,"Active Headers"
  316.     ,headers-deleted);
  317. printf("%-35.35s ( ): %lu\n"
  318.     ,"Header Records"
  319.     ,headers);
  320. printf("%-35.35s ( ): %lu\n"
  321.     ,"Deleted Headers"
  322.     ,deleted);
  323. printf("%-35.35s ( ): %-5lu (%lu bytes)\n"
  324.     ,"Deleted Header Blocks"
  325.     ,delhdrblocks,delhdrblocks*SHD_BLOCK_LEN);
  326. printf("%-35.35s ( ): %-5lu (%lu bytes)\n"
  327.     ,"Deleted Data Blocks"
  328.     ,deldatblocks,deldatblocks*SDT_BLOCK_LEN);
  329. if(orphan)
  330.     printf("%-35.35s (!): %lu\n"
  331.         ,"Orphaned Headers"
  332.         ,orphan);
  333. if(idxzeronum)
  334.     printf("%-35.35s (!): %lu\n"
  335.         ,"Zeroed Index Numbers"
  336.         ,idxzeronum);
  337. if(zeronum)
  338.     printf("%-35.35s (!): %lu\n"
  339.         ,"Zeroed Header Numbers"
  340.         ,zeronum);
  341. if(delidx)
  342.     printf("%-35.35s (!): %lu\n"
  343.         ,"Deleted Index Records"
  344.         ,delidx);
  345. if(idxofferr)
  346.     printf("%-35.35s (!): %lu\n"
  347.         ,"Invalid Index Offsets"
  348.         ,idxofferr);
  349. if(dupenum)
  350.     printf("%-35.35s (!): %lu\n"
  351.         ,"Duplicate Index Numbers"
  352.         ,dupenum);
  353. if(dupeoff)
  354.     printf("%-35.35s (!): %lu\n"
  355.         ,"Duplicate Index Offsets"
  356.         ,dupeoff);
  357. if(dupenumhdr)
  358.     printf("%-35.35s (!): %lu\n"
  359.         ,"Duplicate Header Numbers"
  360.         ,dupenumhdr);
  361. if(misnumbered)
  362.     printf("%-35.35s (!): %lu\n"
  363.         ,"Misordered Index Numbers"
  364.         ,misnumbered);
  365. if(lockerr)
  366.     printf("%-35.35s (!): %lu\n"
  367.         ,"Unlockable Header Records"
  368.         ,lockerr);
  369. if(hdrerr)
  370.     printf("%-35.35s (!): %lu\n"
  371.         ,"Unreadable Header Records"
  372.         ,hdrerr);
  373. if(idxnumerr)
  374.     printf("%-35.35s (!): %lu\n"
  375.         ,"Out-Of-Range Index Numbers"
  376.         ,idxnumerr);
  377. if(hdrnumerr)
  378.     printf("%-35.35s (!): %lu\n"
  379.         ,"Out-Of-Range Header Numbers"
  380.         ,hdrnumerr);
  381. if(attr)
  382.     printf("%-35.35s (!): %lu\n"
  383.         ,"Mismatched Header Attributes"
  384.         ,attr);
  385. if(timeerr)
  386.     printf("%-35.35s (!): %lu\n"
  387.         ,"Mismatched Header Import Time"
  388.         ,timeerr);
  389. if(datactalloc)
  390.     printf("%-35.35s (!): %lu\n"
  391.         ,"Misallocated Active Data Blocks"
  392.         ,datactalloc);
  393. if(actalloc)
  394.     printf("%-35.35s (!): %lu\n"
  395.         ,"Misallocated Active Header Blocks"
  396.         ,actalloc);
  397. if(delalloc)
  398.     printf("%-35.35s (!): %lu\n"
  399.         ,"Misallocated Deleted Header Blocks"
  400.         ,delalloc);
  401.  
  402. printf("\n%s Message Base ",smb_file);
  403. if((headers-deleted)!=status.total_msgs || total!=status.total_msgs
  404.     || (headers-deleted)!=total || idxzeronum || zeronum
  405.     || orphan || delidx || dupenumhdr || dupenum || dupeoff || attr
  406.     || lockerr || hdrerr || hdrnumerr || idxnumerr || idxofferr
  407.     || actalloc || delalloc || datactalloc || misnumbered || timeerr) {
  408.     printf("%shas Errors!\n",beep);
  409.     errors++; }
  410. else
  411.     printf("is OK\n");
  412.  
  413. smb_unlocksmbhdr();
  414. smb_close();
  415. }
  416. if(pause_on_error && errlast!=errors) {
  417.     printf("\7\nHit any key to continue...");
  418.     if(!getch())
  419.         getch();
  420.     printf("\n"); }
  421. return(errors);
  422. }
  423.